package com.java.service.impl;

import com.alibaba.excel.EasyExcel;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.java.config.ExcelLisenters;
import com.java.exceptioin.SrbException;
import com.java.pojo.entity.Dict;
import com.java.mapper.DictMapper;
import com.java.pojo.vo.DictVo;
import com.java.result.ResultCodeEnum;
import com.java.service.DictService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.multipart.MultipartFile;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletResponse;
import java.io.InputStream;
import java.io.UnsupportedEncodingException;
import java.net.URLEncoder;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.TimeUnit;

/**
 * <p>
 * 数据字典 服务实现类
 * </p>
 *
 * @author Helen
 * @since 2021-07-08
 */
@Service
public class DictServiceImpl extends ServiceImpl<DictMapper, Dict> implements DictService {

    private static final Logger log1 = LoggerFactory.getLogger(DictServiceImpl.class);
    @Resource
    private DictMapper dictMapper;

    @Resource
    private RedisTemplate redisTemplate;

    //数据字典
    @Override
    public List<Dict> getDicts(Long id) {

        List<Dict> dictList = null;
        try {
            dictList = (List<Dict>)redisTemplate.opsForValue().get("srb:core:dictList"+id);
            log1.info("从redis中取值");
            if(dictList!=null)return dictList;
        } catch (Exception e) {
            log1.info("服务器异常", e);//此处不抛出异常继续往下走
        }
        //取值
        QueryWrapper<Dict> wrapper = new QueryWrapper<>();
        wrapper.eq("parent_id",id);
        List<Dict> dicts = dictMapper.selectList(wrapper);
        for(Dict dict : dicts){
            Boolean hasChildren =  fetchChildData(dict.getId());
            dict.setHasChildren(hasChildren);
        }
        try {
            redisTemplate.opsForValue().set("srb:core:dictList"+id,dicts,5, TimeUnit.MINUTES);
        }catch (Exception e){
            new SrbException(ResultCodeEnum.SERVICE_ERROR);//抛出服务异常
        }
        return dicts;
    }

    //导出
    @Override
    public void export(HttpServletResponse response) {
        try {
            // 这里注意 有同学反应使用swagger 会导致各种问题，请直接用浏览器或者用postman
            response.setContentType("application/vnd.ms-excel");
            response.setCharacterEncoding("utf-8");
            // 这里URLEncoder.encode可以防止中文乱码 当然和easyexcel没有关系
            String fileName = URLEncoder.encode("mydict", "UTF-8").replaceAll("\\+", "%20");
            response.setHeader("Content-disposition", "attachment;filename*=utf-8''" + fileName + ".xlsx");
            List<Dict> dictList = dictMapper.selectList(null);
            List<DictVo> DictVoList = new ArrayList<>(dictList.size());//指定了list长度
            for(Dict dict : dictList){
                DictVo dictVo = new DictVo();
                BeanUtils.copyProperties(dict,dictVo);
                DictVoList.add(dictVo);
            }
            EasyExcel.write(response.getOutputStream(),DictVo.class).sheet(0,"数据字典").doWrite(DictVoList);
        }catch(Exception e){
            e.printStackTrace();
        }
    }

    //导入
    @Transactional(rollbackFor = {Exception.class})//要么全部导入成功 错了一个要么全部撤回
    @Override
    public void importExcel(InputStream inputStream) {
        EasyExcel.read(inputStream, DictVo.class, new ExcelLisenters(dictMapper)).sheet().doRead();
    }

    @Override
    public List<Dict> getDictsByDictCode(String dictCode) {

        QueryWrapper<Dict> wrapper = new QueryWrapper<>();
        wrapper.eq("dict_code",dictCode);
        Dict dict = dictMapper.selectOne(wrapper);
        return this.getDicts(dict.getId());
    }

    private Boolean fetchChildData(Long id){
        QueryWrapper<Dict> wrapper = new QueryWrapper<>();
        wrapper.eq("parent_id",id);
        Integer count = dictMapper.selectCount(wrapper);
        return count > 0;
    }

    @Override
    public String  getNameByParentDictCodeAndValue(String dictCode,Integer value){
        //
        QueryWrapper<Dict> wrapper = new QueryWrapper<>();
        wrapper.eq("dict_code",dictCode);
        Dict parentDict = dictMapper.selectOne(wrapper);
        if(parentDict == null){
            return "";
        }
        wrapper = new QueryWrapper<>();
        wrapper.eq("parent_id",parentDict.getId())
                .eq("value",value);
        Dict dict = dictMapper.selectOne(wrapper);
        if(dict == null){
            return "";
        }
        return dict.getName();
    }
}
